package com.tiny.tinyweb.core.dao.access;

import com.tiny.tinyweb.core.exception.DaoException;



/**
 * 实现动态构造SQL语句的<code>ORDER BY</code>子句的辅助类。
 * @author wxiaobin
 */
public final class SortHelper {
    /**
     * 提供<code>ORDER BY</code>语句中排序类型的类。使用<code>int</code>型“1”表示“ASC”,“2”表示“DESC”。
     */
    public static class Type {
        /**
         * SQL语句的排序类型，默认值为“ASC”。
         */
        @SuppressWarnings("unused")
        private int type = 1;

        /**
         * 用来设置排序类型的构造器。
         * @param type 排序类型
         */
        private Type(int type) {
            this.type = type;
        }

        /**
         * 升序ASC。
         */
        public static final Type ASC = new Type(1);

        /**
         * 降序DESC。
         */
        public static final Type DESC = new Type(2);
    }

    /**
     * 用来排序的字段。
     */
    private String column;

    /**
     * 排序类型。
     */
    private Type type;

    /**
     * 获得排序的字段的值。
     * @return 排序的字段的值
     */
    public String getColumn() {
        if (this.column == null || this.column.isEmpty()) {
            throw new DaoException("The column must not be null or empty.");
        }
        return column;
    }

    /**
     * 设置排序字段的值。
     * @param column 排序字段的新值
     */
    public void setColumn(String column) {
        this.column = column;
    }

    /**
     * 获得排序类型的值。
     * @return 排序类型的值
     */
    public Type getType() {
        return this.type;
    }

    /**
     * 设置排序类型的值
     *
     * @param type 排序类型的新值
     */
    public void setType(Type type) {
        this.type = type;
    }

    /**
     * 默认的无参构造器，初始化排序类型为升序（ASC）。
     */
    public SortHelper() {
        this.type = Type.ASC;
    }

    /**
     * 指定排序字段和排序类型的构造器。
     *
     * @param column 排序字段名称
     * @param type 排序类型对象
     */
    public SortHelper(String column, Type type) {
        this.column = column;
        this.type = type;
    }

    /**
     * 根据排序类型对象，获得SQL语句的排序关键字。如果不是“ASC”或“DESC”，抛出值无效的异常。
     *
     * @return ASC 或 DESC
     */
    public String getSqlType() {
        if (this.type == Type.ASC) {
            return "ASC";
        } else if (this.type == Type.DESC) {
            return "DESC";
        } else {
            throw new DaoException(String.format(
                    "Sorting type '%1$s' is invalid. It must be ASC or DESC.", this.type));
        }
    }

    @Override
    public String toString() {
        StringBuilder sb = new StringBuilder();
        sb.append(super.toString()).append("[");
        sb.append("COLUMN=").append(this.column).append(", ");
        sb.append("TYPE=");
        if (this.type == Type.ASC) {
            sb.append("ASC");
        } else if (this.type == Type.DESC) {
            sb.append("DESC");
        } else {
            sb.append(this.type);
        }
        sb.append("]");
        return sb.toString();
    }
}
